home *** CD-ROM | disk | FTP | other *** search
/ FishMarket 1.0 / FishMarket v1.0.iso / fishies / 476-500 / disk_500 / wiconify / wiconify-source.lzh / Source / wEvent.c < prev    next >
C/C++ Source or Header  |  1991-04-19  |  22KB  |  788 lines

  1. /*
  2.  *  WICONIFY    A utility that allows you to iconify any Intuition window
  3.  *              on any screen, and to open WB windows on any screen.
  4.  *
  5.  *  wEvent.c    Main event loop routines.
  6.  *
  7.  *  Copyright 1990 by Davide P. Cervone, all rights reserved.
  8.  *  You may use this code, provided this copyright notice is kept intact.
  9.  */
  10.  
  11. #include "wHandler.h"
  12. #include "wMenu.h"
  13.  
  14. static char *IconAbout = COPYRIGHT;     /* ABOUT... message */
  15.  
  16. static WORD MouseX,MouseY;              /* Saved mouse position */
  17. static WSCREEN *MouseScreen = NULL;     /* Screen where mouse move occured */
  18. static WICONREF *PressedIcon;           /* Icon to report a release event to */
  19.  
  20. static WICON NullIcon = {NULL, NULL,NULL,NULL, 0,0,0, 0,NULL};
  21.                                         /* an empty icon structure */
  22.  
  23. extern struct Window *WindowToActivate;
  24.  
  25.  
  26. /*
  27.  *  DoVanillaKey()
  28.  *
  29.  *  Then, if the right amiga key was pressed, and no shift is pressed,
  30.  *    Attempt to create a new screen of the required depth
  31.  *    If successful, activate the wIconify window on the screen
  32.  */
  33.  
  34. static void DoVanillaKey(Code,Qualifier,theWindow)
  35. USHORT Code;
  36. USHORT Qualifier;
  37. struct Window *theWindow;
  38. {
  39.    WSCREEN *theScreen;
  40.  
  41.    if (Code >= '1' && Code <= '5')
  42.    {
  43.       if ((Qualifier & (AMIGARIGHT | SHIFTKEYS)) == AMIGARIGHT)
  44.       {
  45.          Code -= '0';
  46.          theScreen = DoNewScreen(Code,theWindow->WScreen);
  47.          if (theScreen && theScreen->BackDrop)
  48.             ActivateWindow(theScreen->BackDrop);
  49.       }
  50.    }
  51. }
  52.  
  53.  
  54. /*
  55.  *  DoMouseButtons()
  56.  *
  57.  *  Do the right thing for each of the event types:
  58.  *  SELECTDOWN:
  59.  *    Cancel any drag in progress (never should happen)
  60.  *    If there are any icons selected, deselect them
  61.  *
  62.  *  SELECTUP:
  63.  *    If there is an icon to report a release event to, do it
  64.  *    Complete any dragging that is in progress
  65.  *    If there is a window to activate (due to a double-click), do it
  66.  *      (we wait until now so that the window does not get an unexpected
  67.  *      SELECTUP message when the mouse is released)
  68.  *
  69.  *  MENUDOWN:
  70.  *    Cancel any dragging in progress
  71.  *
  72.  *  MENUUP:
  73.  *    Cancel any dragging and close any selected icons (the only time we will
  74.  *    get menu buttons rather than menu events is when an icon is being 
  75.  *    dragged)
  76.  */
  77.  
  78. static void DoMouseButtons(theMessage,theScreen)
  79. struct IntuiMessage *theMessage;
  80. WSCREEN *theScreen;
  81. {
  82.    switch(theMessage->Code)
  83.    {
  84.       case SELECTDOWN:
  85.          CancelDragging(theScreen);
  86.          if (theScreen->Selected) DeselectAll(theScreen);
  87.          break;
  88.  
  89.       case SELECTUP:
  90.          if (PressedIcon) ReportEvent(WI_REPORTRELEASE,PressedIcon);
  91.          EndDragging(theScreen,theMessage->MouseX,theMessage->MouseY);
  92.          if (WindowToActivate)
  93.             ActivateWindow(WindowToActivate),
  94.             WindowToActivate = NULL;
  95.          break;
  96.  
  97.       case MENUDOWN:
  98.          CancelDragging(theScreen);
  99.          break;
  100.  
  101.       case MENUUP:
  102.          CancelDragging(theScreen);
  103.          CloseSelected(theScreen);
  104.          break;
  105.    }
  106.    PressedIcon = NULL;
  107. }
  108.  
  109.  
  110.  
  111. /*
  112.  *  DoMouseMove()
  113.  *
  114.  *  If mouse moves have occured,
  115.  *    If icons are being dragged on the given screen,
  116.  *      Move them to their new location
  117.  *    Reset for next move
  118.  */
  119.  
  120. void DoMouseMove()
  121. {
  122.    if (MouseScreen)
  123.    {
  124.       if (MouseScreen->Flags & (WI_STARTDRAG| WI_DRAGGING))
  125.          MoveGels(MouseScreen,MouseX,MouseY);
  126.       MouseScreen = NULL;
  127.    }
  128. }
  129.  
  130.  
  131. /*
  132.  *  EARLIERTIME checks if one time value is earlier than another.
  133.  */
  134. #define EARLIERTIME(s1,m1,s2,m2)    ((s1)<(s2)||((s1)==(s2)&&(m1)<(m2)))
  135.  
  136.  
  137. /*
  138.  *  DoGadgetDown()
  139.  *
  140.  *  If the current message time is earlier than the previous time (ie, the
  141.  *    clock has been reset), then if the time is not zero (ie, it is not a
  142.  *    bogus time stamp from some other input handler) then clear the old times
  143.  *  If we have a double click
  144.  *    Cancel dragging in progress (never should happen)
  145.  *    Open the list of selected gadgets, but wait to activate the windows
  146.  *      until we get a mouse up event
  147.  *  Otherwise
  148.  *    If the gadget wants press events reported,
  149.  *      Report the event and save the pressed gadget for a release event
  150.  *    Select the pressed gadget
  151.  *    If the gadget has been selected, set up for dragging it
  152.  *    Record the time for double click checking.
  153.  */
  154.  
  155. static void DoGadgetDown(theGadget,theScreen,theMessage)
  156. struct wGadget *theGadget;
  157. WSCREEN *theScreen;
  158. struct IntuiMessage *theMessage;
  159. {
  160.    static long Secs = 0, Mics = 0;
  161.  
  162.    if (EARLIERTIME(theMessage->Seconds,theMessage->Micros,Secs,Mics))
  163.       if (theMessage->Seconds || theMessage->Micros) Secs = Mics = 0;
  164.    if (DoubleClick(Secs,Mics,theMessage->Seconds,theMessage->Micros))
  165.    {
  166.       CancelDragging(theScreen);
  167.       OpenSelected(theScreen,FALSE);
  168.    } else {
  169.       if (GADGETICON->Icon.Report & WI_REPORTPRESS)
  170.       {
  171.          ReportEvent(WI_REPORTPRESS,GADGETICON);
  172.          PressedIcon = GADGETICON;
  173.       }
  174.       SelectIcon(GADGETICON,theMessage->Qualifier & SHIFTKEYS);
  175.       if (theGadget->Gadget.Flags & SELECTED)
  176.          StartDragging(GADGETICON,theMessage->MouseX,theMessage->MouseY);
  177.       Secs = theMessage->Seconds;
  178.       Mics = theMessage->Micros;
  179.    }
  180. }
  181.  
  182.  
  183. /*
  184.  *  DoIconMenu()
  185.  *
  186.  *  Do the right thing for each of the menu items (the routine names are
  187.  *  pretty self-explanitory).
  188.  */
  189.  
  190. static int DoIconMenu(theCode,theScreen,EndItAll)
  191. USHORT theCode;
  192. WSCREEN *theScreen;
  193. int EndItAll;
  194. {
  195.    switch(ITEMNUM(theCode))
  196.    {
  197.       case IM_OPEN:
  198.          OpenSelected(theScreen,TRUE);
  199.          break;
  200.  
  201.       case IM_CLOSE:
  202.          CloseSelected(theScreen);
  203.          break;
  204.  
  205.       case IM_LOCK:
  206.          LockSelected(theScreen);
  207.          UpdateActiveMenu();
  208.          break;
  209.  
  210.       case IM_CLEANUP:
  211.          CleanUpIcons(theScreen);
  212.          RefreshIcons(theScreen,TRUE);
  213.          break;
  214.  
  215.       case IM_ORGANIZE:
  216.          OrganizeIcons(theScreen);
  217.          RefreshIcons(theScreen,TRUE);
  218.          break;
  219.  
  220.       case IM_OPENALL:
  221.          OpenAllIcons(theScreen);
  222.          break;
  223.  
  224.       case IM_ABOUT:
  225.          if (ActiveWindow)
  226.          {
  227.             SetWindowTitles(ActiveWindow,-ONE,IconAbout);
  228.             ShowTitle(ActiveWindow->WScreen,TRUE);
  229.          }
  230.          break;
  231.  
  232.       case IM_END:
  233.          DoEndIconify();
  234.          break;
  235.    }
  236.    return(EndItAll);
  237. }
  238.  
  239.  
  240. /*
  241.  *  DoMenu()
  242.  *
  243.  *  While there are more menu items to do
  244.  *    Get the menu item pointer
  245.  *    If it is an ICON menu item, do the ICON menu code
  246.  *    Otherwise do the SCREEN menu code
  247.  *    Go on to the next item
  248.  */
  249.  
  250. static int DoMenu(theCode,theScreen,EndItAll)
  251. USHORT theCode;
  252. WSCREEN *theScreen;
  253. int EndItAll;
  254. {
  255.    struct MenuItem *theItem;
  256.  
  257.    while (theCode != MENUNULL)
  258.    {
  259.       theItem = ItemAddress(wMenu,theCode);
  260.       switch(MENUNUM(theCode))
  261.       {
  262.          case ICON_MENU:
  263.             EndItAll = DoIconMenu(theCode,theScreen,EndItAll);
  264.             break;
  265.  
  266.          case SCREEN_MENU:
  267.             EndItAll = DoScreenMenu(theCode,theScreen,EndItAll);
  268.             break;
  269.       }
  270.       theCode = theItem->NextSelect;
  271.    }
  272.    return(EndItAll);
  273. }
  274.  
  275.  
  276. /*
  277.  *  DoEvent()
  278.  *
  279.  *  Clear the ABOUT or error message from the screen title, if necessary
  280.  *  Get the screen of the wIconify window were the message occured
  281.  *  If the screen exists
  282.  *    If there are pending mouse moves and this is not a mouse move
  283.  *      Do the buffered mouse moves
  284.  *    Call the correct routine for each class of events
  285.  */
  286.  
  287. int DoEvent(theMessage,EndItAll)
  288. struct IntuiMessage *theMessage;
  289. int EndItAll;
  290. {
  291.    WSCREEN *theScreen;
  292.  
  293.    if (ActiveWindow && ActiveWindow->ScreenTitle != wIconifyTitle)
  294.       SetWindowTitles(ActiveWindow,-ONE,wIconifyTitle);
  295.    theScreen = (WSCREEN *)theMessage->IDCMPWindow->UserData;
  296.    if (theScreen)
  297.    {
  298.       if (MouseScreen && theMessage->Class != MOUSEMOVE) DoMouseMove();
  299.       switch(theMessage->Class)
  300.       {
  301.          case MOUSEBUTTONS:
  302.             DoMouseButtons(theMessage,theScreen);
  303.             break;
  304.  
  305.          case GADGETDOWN:
  306.             DoGadgetDown(theMessage->IAddress,theScreen,theMessage);
  307.             break;
  308.  
  309.          case MENUPICK:
  310.             CancelDragging(theScreen);
  311.             EndItAll = DoMenu(theMessage->Code,theScreen,EndItAll);
  312.             break;
  313.  
  314.          case MOUSEMOVE:
  315.             MouseX = theMessage->MouseX;
  316.             MouseY = theMessage->MouseY;
  317.             MouseScreen = theScreen;
  318.             break;
  319.  
  320.          case VANILLAKEY:
  321.             DoVanillaKey(theMessage->Code,theMessage->Qualifier,
  322.                          theMessage->IDCMPWindow);
  323.             break;
  324.  
  325.          case ACTIVEWINDOW:
  326.             SetActiveWindow(theMessage->IDCMPWindow);
  327.             WindowToActivate = NULL;
  328.             break;
  329.  
  330.          case INACTIVEWINDOW:
  331.             SetActiveWindow(NULL);
  332.             WindowToActivate = NULL;
  333.             break;
  334.       }
  335.    }
  336.    return(EndItAll);
  337. }
  338.  
  339.  
  340. /*
  341.  *  DoIconify()
  342.  *
  343.  *  Get the icon and screen of the given window
  344.  *  If the screen was located
  345.  *    but there was no icon for the window
  346.  *       Create a new icon structure, if possible
  347.  *          Make it point to the given window
  348.  *          Set its default flags and mark it as system-created
  349.  *          And link it into the icon list for its screen
  350.  *    If an icon exists or was allocated
  351.  *      If the icon is for a screen and dragging is in progress (ie, the
  352.  *          left button is down over an icon), and the message is a NOREPLY
  353.  *          message (ie, it came from the handler), then
  354.  *        Close the selected icons on the screen
  355.  *      Otherwise
  356.  *        If the icon wants to verify iconifications, report ICONVERIFY
  357.  *        Otherwise iconify the window
  358.  */
  359.  
  360. void DoIconify(theMessage)
  361. struct wIconMessage *theMessage;
  362. {
  363.    WICONREF *theIcon;
  364.    WSCREEN *theScreen;
  365.  
  366.    theIcon = FindIcon(theMessage->Window,&theScreen);
  367.    if (theScreen)
  368.    {
  369.       if (theIcon == NULL)
  370.       {
  371.          if (NEWSTRUCT(wIconRef,theIcon))
  372.          {
  373.             theIcon->Window = theMessage->Window;
  374.             theIcon->Icon.Flags |= WI_SYSICON | DefaultFlags;
  375.             LinkIcon(theIcon,theScreen);
  376.          }
  377.       }
  378.       if (theIcon)
  379.       {
  380.          if ((theIcon->Icon.Flags & WI_SCREENICON) &&
  381.              (theIcon->Screen->Flags & (WI_STARTDRAG | WI_DRAGGING)) &&
  382.              (theMessage->Flags & WI_NOREPLY))
  383.          {
  384.             CloseSelected(theIcon->Screen);
  385.          } else {
  386.             if (theIcon->Icon.Report & WI_REPORTICONVERIFY)
  387.                ReportEvent(WI_REPORTICONVERIFY,theIcon);
  388.               else
  389.                Iconify(theIcon,theMessage->Flags & WI_CHANGE);
  390.          }
  391.       }
  392.    }
  393. }
  394.  
  395.  
  396. /*
  397.  *  UpdateIcon()
  398.  *
  399.  *  If there was no icon given, use the blank icon
  400.  *  Get the icon's screen and system flags
  401.  *  Copy the icon template to the existing icon
  402.  *  And replace the system flags from before
  403.  *  If the icon is currently iconified (ie, it has a gadget)
  404.  *    Get the gadget pointer
  405.  *    Remove the gadget temprarily so we can work on it
  406.  *    If no new position was given, retrieve the old one
  407.  *    Save the SELECTED flag
  408.  *    Setup the gadget to use the current icon data
  409.  *    If it used to be selected, re-select it
  410.  *    Replace the gadget on the screen and refresh the screen's icons
  411.  */
  412.  
  413. static void UpdateIcon(theIcon,WIcon)
  414. WICONREF *theIcon;
  415. WICON *WIcon;
  416. {
  417.    WSCREEN *theScreen;
  418.    ULONG Flags;
  419.    int pos;
  420.    struct Gadget *theGadget;
  421.    
  422.    if (WIcon == NULL) WIcon = &NullIcon;
  423.    theScreen = theIcon->Screen;
  424.    Flags = theIcon->Icon.Flags & WI_SYSTEMFLAGS;
  425.    theIcon->Icon = *WIcon;
  426.    theIcon->Icon.Flags = (WIcon->Flags & ~WI_SYSTEMFLAGS) | Flags;
  427.    if (theIcon->Gadget)
  428.    {
  429.       theGadget = &(theIcon->Gadget->Gadget);
  430.       if (theScreen->BackDrop)
  431.           pos = RemoveGadget(theScreen->BackDrop,theGadget);
  432.       if (WIcon->x == 0 && WIcon->y == 0)
  433.          theIcon->Icon.x = theGadget->LeftEdge,
  434.          theIcon->Icon.y = theGadget->TopEdge;
  435.       Flags = theGadget->Flags & SELECTED;
  436.       SetupGadget(theIcon);
  437.       if (Flags) MakeSelected(theGadget);
  438.       if (theScreen->BackDrop) AddGadget(theScreen->BackDrop,theGadget,pos);
  439.       RefreshIcons(theScreen,TRUE);
  440.    }
  441. }
  442.  
  443.  
  444. /*
  445.  *  DoSetIcon()
  446.  *
  447.  *  Find the icon and screen of the given window
  448.  *  If the icon already exists, update it to the new values,
  449.  *  Otherwise, if the screen was found
  450.  *    Get a new Icon structure, if possible
  451.  *      Link it to the window
  452.  *      Copy the data from the template
  453.  *      Clear the system flags
  454.  *      If no template was given, add the default flags
  455.  *      Link the icon to the screen's icon list
  456.  *  Return the pointer to the IconRef structure
  457.  */
  458.  
  459. static void DoSetIcon(theWindow,WIcon,theMessage)
  460. struct Window *theWindow;
  461. WICON *WIcon;
  462. struct wIconMessage *theMessage;
  463. {
  464.    WICONREF *theIcon;
  465.    WSCREEN *theScreen;
  466.    
  467.    theIcon = FindIcon(theWindow,&theScreen);
  468.    if (theIcon) UpdateIcon(theIcon,WIcon);
  469.    else if (theScreen)
  470.    {
  471.       if (NEWSTRUCT(wIconRef,theIcon))
  472.       {
  473.          theIcon->Window = theWindow;
  474.          theIcon->Icon = (WIcon)? *WIcon: NullIcon;
  475.          theIcon->Icon.Flags &= ~WI_SYSTEMFLAGS;
  476.          if (WIcon == NULL) theIcon->Icon.Flags |= DefaultFlags;
  477.          LinkIcon(theIcon,theScreen);
  478.       }
  479.    }
  480.    theMessage->Icon = theIcon;
  481. }
  482.  
  483.  
  484. /*
  485.  *  DoUnSetIcon()
  486.  *
  487.  *  Find the icon and screen of the given window
  488.  *  If the icon was found
  489.  *    Restore the icon's window and remove the icon from the screen
  490.  *    Delete the icon from memory
  491.  *  Return the IconRef (which is no longer valid)
  492.  */
  493.  
  494. static void DoUnSetIcon(theWindow,theMessage)
  495. struct Window *theWindow;
  496. struct wIconMessage *theMessage;
  497. {
  498.    WICONREF *theIcon;
  499.  
  500.    theIcon = FindIcon(theMessage->Window,&(theMessage->Data.wScreen));
  501.    if (theIcon)
  502.    {
  503.       Restore(theIcon,TRUE);
  504.       DeleteIcon(theIcon);
  505.    }
  506.    theMessage->Icon = theIcon;
  507. }
  508.  
  509.  
  510. /*
  511.  *  DoAddIcon()
  512.  *
  513.  *  If a screen and an icon are given
  514.  *    Create a new Icon structure
  515.  *      Mark it as having no window associated with it
  516.  *      Copy the template icon
  517.  *      Clear the system flags
  518.  *      Link the icon into the screen's icon list
  519.  *      Iconify the icon (ie, make it show up on the screen
  520.  *  Return the newly created IconRef
  521.  */
  522.  
  523. static WICONREF *DoAddIcon(WIcon,theScreen)
  524. WICON *WIcon;
  525. WSCREEN *theScreen;
  526. {
  527.    WICONREF *theIcon = NULL;
  528.  
  529.    if (theScreen && WIcon)
  530.    {
  531.       if (NEWSTRUCT(wIconRef,theIcon))
  532.       {
  533.          theIcon->Window = NULL;
  534.          theIcon->Icon = *WIcon;
  535.          theIcon->Icon.Flags &= ~WI_SYSTEMFLAGS;
  536.          LinkIcon(theIcon,theScreen);
  537.          Iconify(theIcon,FALSE);
  538.       }
  539.    }
  540.    return(theIcon);
  541. }
  542.  
  543.  
  544. /*
  545.  *  DoSelectNext()
  546.  *
  547.  *  If the screen has selected icons, start with the next one,
  548.  *  Otherwise start with the first icon on the screen
  549.  *  Skip over any non-iconified icons
  550.  *  If we hit the end of the list of icons
  551.  *    Start over at the begining of the list
  552.  *    Skip over any non-iconified icons (until we get back to were we started)
  553.  *  If we found a new icon to select, select it
  554.  */
  555.  
  556. static void DoSelectNext(theScreen)
  557. WSCREEN *theScreen;
  558. {
  559.    WICONREF *theIcon,*InitialIcon;
  560.  
  561.    if (theScreen->Selected)
  562.       InitialIcon = ((WICONREF *)(theScreen->Selected->Gadget.UserData))->Next;
  563.      else
  564.       InitialIcon = theScreen->IconRef;
  565.    theIcon = InitialIcon;
  566.    while (theIcon && (theIcon->Icon.Flags & WI_ICONIFIED) == FALSE)
  567.       theIcon = theIcon->Next;
  568.    if (theIcon == NULL)
  569.    {
  570.       theIcon = theScreen->IconRef;
  571.       while (theIcon && (theIcon->Icon.Flags & WI_ICONIFIED) == FALSE &&
  572.          theIcon != InitialIcon) theIcon = theIcon->Next;
  573.    }
  574.    if (theIcon) SelectIcon(theIcon,FALSE);
  575. }
  576.  
  577.  
  578. /*
  579.  *  DoIconEvent()
  580.  *
  581.  *  Do the right thing for each type of message
  582.  *  ICONIFY:    Do the iconification routine
  583.  *  RESTORE:    Restore the given icon
  584.  *  ICONOF:     Find the icon and screen of the given window
  585.  *  SETICON:    Set the window's icon
  586.  *  UNSETICON:  Remove the window's icon
  587.  *  SELECTICON: Attempt to select the indicated icon
  588.  *  UNSELECT:   Remove the icon from the selection
  589.  *  MOVEICON:
  590.  *    If an icon was specified
  591.  *      Get the icon's screen
  592.  *      If the icon has a gadget and the screen has a wIconify window
  593.  *         Remove the gadget from the screen
  594.  *         Set the gadget's position to the one given in the message
  595.  *         Check the new position for validity
  596.  *         Put the gadget back on the screen
  597.  *         Refresh the icons on the screen
  598.  *  ADDICON:    Add the given icon to the indicated screen
  599.  *  REMOVEICON: Delete the icon from memory
  600.  *  REDRAW:     Refresh the icons on the given screen
  601.  *  UPDATEICON: Update the given icon with new values
  602.  *  BACKDROPOF:
  603.  *    Find the screen structure if the given screen
  604.  *    If found, return the backdrop window of the screen
  605.  *    Otherwise return NULL
  606.  *  REMSCREEN:  Remove the given screen from the list of screens
  607.  *  CLOSEICON:  Close the given icon
  608.  *  SELECTNEXT: Select the next icon on the given screen
  609.  *  NEWSCREEN:
  610.  *    If the real WB screen is open (to use as a template)
  611.  *      Change the active window (unsetting the menus)
  612.  *      Set the NewScreen menu to the given modes
  613.  *      Create the new screen and return its pointer
  614.  *  MAKEWB:
  615.  *    Find the indicated screen
  616.  *    If it is found and it has a wIconify window
  617.  *      Make this the current WB screen
  618.  *      Set the OpenWindow submenu to make CURRENT_WB checked
  619.  *      Activate the new WB screen's wIconify backdrop window
  620.  *  OPENSELECT:    Open the selected icons on the given screen
  621.  *  CLOSESELECT:   Close the selected icons on the given screen
  622.  *  OPENON:        Set the OpenOn menu items
  623.  *  REPORTVERIFY:  (returned ICONVERIFY message)
  624.  *    If the message was OKed, iconify the window
  625.  *  MAKECONTACT:   (Initial message from the loader)
  626.  *    Check the loader's version and report OK or BAD
  627.  *  ENDICONIFY:
  628.  *    Try to end the process
  629.  *    Report to any programs that are interested
  630.  *    Try to exit when we have cleaned out all message from the ports
  631.  */
  632.  
  633. int DoIconEvent(theMessage,EndItAll)
  634. struct wIconMessage *theMessage;
  635. int EndItAll;
  636. {
  637.    WSCREEN *theScreen;
  638.    int pos;
  639.  
  640.    switch(theMessage->Action)
  641.    {
  642.       case WI_ICONIFY:
  643.          DoIconify(theMessage);
  644.          break;
  645.  
  646.       case WI_RESTORE:
  647.          Restore(theMessage->Icon,TRUE);
  648.          break;
  649.  
  650.       case WI_ICONOF:
  651.          theMessage->Icon =
  652.              FindIcon(theMessage->Window,&(theMessage->Data.wScreen));
  653.          break;
  654.  
  655.       case WI_SETICON:
  656.          DoSetIcon(theMessage->Window,theMessage->Icon,theMessage);
  657.          break;
  658.  
  659.       case WI_UNSETICON:
  660.          DoUnSetIcon(theMessage->Window,theMessage);
  661.          break;
  662.  
  663.       case WI_SELECTICON:
  664.          SelectIcon(theMessage->Icon,theMessage->Flags & WI_ADDTOSELECT);
  665.          break;
  666.  
  667.       case WI_UNSELECT:
  668.          DeselectIcon(theMessage->Icon);
  669.          break;
  670.  
  671.       case WI_MOVEICON:
  672.          if (theMessage->Icon)
  673.          {
  674.             theScreen = theMessage->Icon->Screen;
  675.             if (theMessage->Icon->Gadget && theScreen->BackDrop)
  676.             {
  677.                pos = RemoveGadget(theScreen->BackDrop,theMessage->Icon->Gadget);
  678.                theMessage->Icon->Gadget->Gadget.LeftEdge =
  679.                    theMessage->Data.Position.x;
  680.                theMessage->Icon->Gadget->Gadget.TopEdge =
  681.                    theMessage->Data.Position.y;
  682.                InitPosition(theMessage->Icon->Gadget);
  683.                AddGadget(theScreen->BackDrop,theMessage->Icon->Gadget,pos);
  684.                RefreshIcons(theMessage->Icon->Screen,TRUE);
  685.             }
  686.          }
  687.          break;
  688.  
  689.       case WI_ADDICON:
  690.          if (theMessage->Icon) theMessage->Icon =
  691.             DoAddIcon(theMessage->Icon,FindScreen(theMessage->Data.Screen));
  692.          break;
  693.  
  694.       case WI_REMOVEICON:
  695.          if (theMessage->Icon) DeleteIcon(theMessage->Icon);
  696.          break;
  697.  
  698.       case WI_REDRAW:
  699.          RefreshIcons(theMessage->Data.wScreen,TRUE);
  700.          break;
  701.  
  702.       case WI_UPDATEICON:
  703.          if (theMessage->Icon)
  704.             UpdateIcon(theMessage->Icon,theMessage->Data.Icon);
  705.          break;
  706.  
  707.       case WI_BACKDROPOF:
  708.          theScreen = FindScreen(theMessage->Data.Screen);
  709.          if (theScreen)
  710.             theMessage->Window = theScreen->BackDrop;
  711.            else
  712.             theMessage->Window = NULL;
  713.          break;
  714.  
  715.       case WI_REMSCREEN:
  716.          UnLinkScreen(theMessage->Data.wScreen);
  717.          break;
  718.  
  719.       case WI_CLOSEICON:
  720.          CloseIcon(theMessage->Icon);
  721.          break;
  722.  
  723.       case WI_SELECTNEXT:
  724.          theScreen = FindScreen(theMessage->Data.Screen);
  725.          if (theScreen) DoSelectNext(theScreen);
  726.          break;
  727.  
  728.       case WI_NEWSCREEN:
  729.          if (RealWB)
  730.          {
  731.             SetActiveWindow(NULL);
  732.             SetScreenMenu(theMessage->Data.NewScreen.Modes);
  733.             theScreen = 
  734.                DoNewScreen(theMessage->Data.NewScreen.Depth,RealWB->Screen);
  735.             theMessage->Data.Screen = theScreen->Screen;
  736.          }
  737.          break;
  738.  
  739.       case WI_MAKEWB:
  740.          theScreen = FindScreen(theMessage->Data.Screen);
  741.          if (theScreen && theScreen->BackDrop)
  742.          {
  743.             NewWBScreen(theScreen);
  744.             SetWindowMenu(OW_CURRENTWB,NOCHANGE);
  745.             ActivateWindow(theScreen->BackDrop);
  746.          }
  747.          break;
  748.  
  749.       case WI_OPENSELECT:
  750.          OpenSelected(FindScreen(theMessage->Data.Screen),TRUE);
  751.          break;
  752.  
  753.       case WI_CLOSESELECT:
  754.          CloseSelected(FindScreen(theMessage->Data.Screen));
  755.          break;
  756.  
  757.       case WI_OPENON:
  758.          SetWindowMenu(theMessage->Data.OpenOn.ScreenType,
  759.                        theMessage->Data.OpenOn.SizeToFit);
  760.          break;
  761.  
  762.       case WI_REPORTICONVERIFY:
  763.          if (theMessage->Flags & WI_ICONIFYOK)
  764.             Iconify(theMessage->Icon,theMessage->Flags & WI_CHANGE);
  765.          break;
  766.  
  767.       case WI_MAKECONTACT:
  768.          if (theMessage->Data.Version.Maj > MAJLIBVERS ||
  769.             (theMessage->Data.Version.Maj == MAJLIBVERS &&
  770.              theMessage->Data.Version.Min >= MINLIBVERS))
  771.          {
  772.             theMessage->Action = WI_VERSIONOK;
  773.             theMessage->Data.Version.Maj = MAJVERSION;
  774.             theMessage->Data.Version.Min = MINVERSION;
  775.          } else {
  776.             theMessage->Action = WI_VERSIONBAD;
  777.          }
  778.          break;
  779.  
  780.       case WI_ENDICONIFY:
  781.          AttemptEnd(theMessage);
  782.          ReportMulti(WI_REPORTICONEND,NULL,NULL);
  783.          EndItAll = TRUE;
  784.          break;
  785.    }
  786.    return(EndItAll);
  787. }
  788.